package com.ruoyi.material.service.impl;

import com.ruoyi.material.controller.DrawImageController;
import com.ruoyi.material.domain.BaseTagFile;
import com.ruoyi.material.service.*;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import javax.imageio.ImageIO;
import java.awt.*;
import java.awt.image.BufferedImage;
import java.io.*;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
/**
 * @program: MSS
 * @description: 对图片进行标注画框
 * @author: cyl
 * @create: 2021-08-05 17:00
 **/
@Service
public class DrawImageServiceImpl implements IDrawImageService {
    private Logger logger = LoggerFactory.getLogger(DrawImageController.class);
    @Autowired
    private IBaseUpAndDownLoadService baseUpAndDownLoadService;
    //画图
    @Override
    public String drawImage(List<BaseTagFile> list, String path, String imageName) throws IOException {
        String imagePath=baseUpAndDownLoadService.getLocalPath(path);
        File oldFile=new File(imagePath);
        String copyFileName=getCopyFile(imagePath);
        File newFile=new File(copyFileName);
        System.out.println(copyFileName);
        if(newFile.exists()){
            //第N次预览，不用再次复制图片并画框
            String newStr = copyFileName.substring(22);
            newStr = "\\profile\\" + newStr;
            return newStr;
        }else {
            //第1次预览要复制要画框
            String newPath= copyFile(imagePath);
            InputStream in = new FileInputStream(newPath);//图片路径
            BufferedImage image = ImageIO.read(new File(newPath));
            int dw = image.getWidth();
            int dh = image.getHeight();
            Iterator<BaseTagFile> it = list.iterator();
            while (it.hasNext()) {//目前控制标记值为4个的时候才会画框，否则不画出来
                BaseTagFile btf = it.next();
                String[] oldInfoStr = btf.getTagInfo().split(" ");
                Long category = btf.getTagCategory();
                if (oldInfoStr.length != 4) {
                    it.remove();
                } else {
                    Map<String, Double> newInfoMap = transferYolo(oldInfoStr, dw, dh);
                    Graphics g = image.getGraphics();
                    g.setColor(Color.red);//画笔颜色
                    Double[] newInfoDouble = new Double[4];
                    int i = 0;
                    for (String key : newInfoMap.keySet()) {
                        newInfoDouble[i++] = newInfoMap.get(key);
                    }
                    int x = newInfoDouble[2].intValue();
                    int y = newInfoDouble[0].intValue();
                    int w = newInfoDouble[1].intValue();
                    int h = newInfoDouble[3].intValue();
                    g.drawRect(x, y, w, h);
                    Font font = new Font("宋体", Font.BOLD + Font.ITALIC, 30); // 创建字体对象
                    g.setFont(font); // 设置字体
                    g.drawString(category.toString(), x, y); // 绘制文本
                    g.dispose();
                }
            }
            FileOutputStream out = new FileOutputStream(newPath);//输出图片的地址
            logger.info("DrawImageController====drawImage====【输出标记图路径newPath：{" + newPath + "}】");
            ImageIO.write(image, "jpeg", out);
            in.close();
            out.close();
            newPath = newPath.substring(22);
            newPath = "\\profile\\" + newPath;
            return newPath;
        }
    }

    //yolo数据反转化
    @Override
    public Map<String,Double> transferYolo(String[] oldInfoStr,int dw,int dh){
        Double center_x = Double.valueOf(Math.round(Double.parseDouble(oldInfoStr[0]) * dw));
        Double center_y = Double.valueOf(Math.round(Double.parseDouble(oldInfoStr[1]) * dh));
        Double bbox_width = Double.valueOf(Math.round(Double.parseDouble(oldInfoStr[2]) * dw));
        Double bbox_height = Double.valueOf(Math.round(Double.parseDouble(oldInfoStr[3]) * dh));
        Double xmin = (center_x - bbox_width) / 2;
        Double ymin = (center_y - bbox_height) / 2;
        Double xmax = (center_x + bbox_width) / 2;
        Double ymax = (center_y + bbox_height) / 2;
        Double x0 = center_x - Math.abs(xmax - xmin) / 2;
        Double y0 = center_y - Math.abs(ymax - ymin) / 2;
        Map<String,Double> info=new HashMap();
        info.put("x0",x0);
        info.put("y0",y0);
        info.put("w",Math.abs(xmax - xmin));
        info.put("h",Math.abs(ymax - ymin));
        return info;
    }

    //对文件重命名
    @Override
    public File createOrRenameFile(File file, String toPrefix, String toSuffix) {
        File directory = file.getParentFile();
        if (!directory.exists()) {
            if (directory.mkdir()) {
                logger.info("路径不存在且创建成功了");
            }
        }
        File newFile = new File(directory, toPrefix + toSuffix);
        for (int i = 1; newFile.exists() && i < Integer.MAX_VALUE; i++) {
            newFile = new File(directory, toPrefix + '(' + i + ')' + toSuffix);
        }
        if (!file.renameTo(newFile)) {
            logger.info("重命名成功了");
            return file;
        }
        return newFile;
    }
    //获取标记后的图片名称，用于确定是否已存在标记后的图
    @Override
    public String getCopyFile(String imagepath){
        File srcFile = new File(imagepath);
        String []str=getFileInfo(srcFile);
        String toPrefix = "";
        String toSuffix = "";
        for(int i=0;i<str.length;i++){
            if(i==0){
                toPrefix=str[i];
            }else {
                toSuffix=str[i];
            }
        }
        String copyFile=srcFile.getParentFile()+"\\"+toPrefix+"-copy"+toSuffix;
        return copyFile;
    }
    //复制图片文件
    @Override
    public String copyFile(String src)
    {
        File srcFile = new File(src);
        String []str=getFileInfo(srcFile);
        String toPrefix = "";
        String toSuffix = "";
        for(int i=0;i<str.length;i++){
            if(i==0){
                toPrefix=str[i];
            }else {
                toSuffix=str[i];
            }
        }
        File targetFile= new File(srcFile.getParentFile()+"\\"+toPrefix+"-copy"+toSuffix);
        if(targetFile.exists()){
            return targetFile.getAbsolutePath();
        }else {
            logger.info("DrawImageController====copyFile====【标记图文件路径targetFile：{" + targetFile + "}】");
            try {
                logger.info("DrawImageController====copyFile====【原图文件路径srcFile：{" + srcFile + "}】");
                InputStream in = new FileInputStream(src);
                OutputStream out = new FileOutputStream(targetFile);
                byte[] bytes = new byte[1024];
                int len = -1;
                while ((len = in.read(bytes)) != -1) {
                    out.write(bytes, 0, len);
                }
                in.close();
                out.close();
            } catch (FileNotFoundException e) {
                e.printStackTrace();
            } catch (IOException e) {
                e.printStackTrace();
            }
            return targetFile.getAbsolutePath();
        }
    }

    //获取文件名的前缀（文件名）和后缀
    @Override
    public String[] getFileInfo(File file){
        String fileName=file.getName();
        int index = fileName.lastIndexOf(".");
        String toPrefix="";
        String toSuffix="";
        if(index==-1){
            toPrefix=fileName;
        }else{
            toPrefix=fileName.substring(0,index);
            toSuffix=fileName.substring(index,fileName.length());
        }
        return new String[]{toPrefix,toSuffix};
    }
}
